package com.lxk.mall.pms.service.impl;

import cn.hutool.core.util.ObjUtil;
import com.lxk.mall.pms.domain.PmsProductProperty;
import com.lxk.mall.pms.domain.bo.property.PmsProductPropertyBo;
import com.lxk.mall.pms.enums.PmsErrorCodeConstants;
import com.lxk.mall.pms.mapper.PmsProductPropertyMapper;
import com.lxk.mall.pms.service.IPmsProductPropertyService;
import com.lxk.mall.pms.service.IPmsProductPropertyValueService;
import com.lxk.mall.pms.service.IPmsProductSkuService;
import jakarta.annotation.Resource;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import com.lxk.mall.pms.domain.vo.property.PmsProductPropertyVo;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Map;
import java.util.Collection;
import java.util.Set;

/**
 * 商品属性项Service业务层处理
 *
 * @author Lion Li
 * @date 2024-06-06
 */
@RequiredArgsConstructor
@Service
public class PmsProductPropertyServiceImpl implements IPmsProductPropertyService {

    private final PmsProductPropertyMapper baseMapper;

    @Resource
    private IPmsProductSkuService productSkuService;

    @Resource
    @Lazy // 延迟加载，解决循环依赖问题
    private IPmsProductPropertyValueService productPropertyValueService;

    /**
     * 查询商品属性项
     *
     * @param id 主键
     * @return 商品属性项
     */
    @Override
    public PmsProductPropertyVo queryById(Long id) {
        return baseMapper.selectVoById(id);
    }

    /**
     * 分页查询商品属性项列表
     *
     * @param bo        查询条件
     * @param pageQuery 分页参数
     * @return 商品属性项分页列表
     */
    @Override
    public TableDataInfo<PmsProductPropertyVo> queryPageList(PmsProductPropertyBo bo, PageQuery pageQuery) {
        LambdaQueryWrapper<PmsProductProperty> lqw = buildQueryWrapper(bo);
        lqw.orderByDesc(PmsProductProperty::getId);
        Page<PmsProductPropertyVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
        return TableDataInfo.build(result);
    }

    /**
     * 查询符合条件的商品属性项列表
     *
     * @param bo 查询条件
     * @return 商品属性项列表
     */
    @Override
    public List<PmsProductPropertyVo> queryList(PmsProductPropertyBo bo) {
        LambdaQueryWrapper<PmsProductProperty> lqw = buildQueryWrapper(bo);
        return baseMapper.selectVoList(lqw);
    }

    private LambdaQueryWrapper<PmsProductProperty> buildQueryWrapper(PmsProductPropertyBo bo) {
        Map<String, Object> params = bo.getParams();
        LambdaQueryWrapper<PmsProductProperty> lqw = Wrappers.lambdaQuery();
        lqw.like(StringUtils.isNotBlank(bo.getName()), PmsProductProperty::getName, bo.getName());
        lqw.eq(bo.getStatus() != null, PmsProductProperty::getStatus, bo.getStatus());
        return lqw;
    }

    /**
     * 新增商品属性项
     *
     * @param bo 商品属性项
     * @return 是否新增成功
     */
    @Override
    public Long insertByBo(PmsProductPropertyBo bo) {
        PmsProductProperty add = MapstructUtils.convert(bo, PmsProductProperty.class);
        // 如果已经添加过该属性项，直接返回
        PmsProductProperty dbProperty = baseMapper.selectByName(add.getName());
        if (dbProperty != null) {
            return dbProperty.getId();
        }
        // 插入
        baseMapper.insert(add);
        // 返回
        return add.getId();
    }

    /**
     * 修改商品属性项
     *
     * @param bo 商品属性项
     * @return 是否修改成功
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean updateByBo(PmsProductPropertyBo bo) {
        PmsProductProperty update = MapstructUtils.convert(bo, PmsProductProperty.class);
        validatePropertyExists(update.getId());
        // 校验名字重复
        PmsProductProperty property = baseMapper.selectByName(update.getName());
        if (property != null &&
            ObjUtil.notEqual(property.getId(), update.getId())) {
            throw new ServiceException(PmsErrorCodeConstants.PROPERTY_EXISTS);
        }
        // 更新
        baseMapper.updateById(update);
        // 更新 sku 相关属性
        productSkuService.updateSkuProperty(update.getId(), update.getName());
        return Boolean.TRUE;
    }

    private void validatePropertyExists(Long id) {
        if (baseMapper.selectById(id) == null) {
            throw new ServiceException(PmsErrorCodeConstants.PROPERTY_NOT_EXISTS);
        }
    }

    /**
     * 保存前的数据校验
     */
    private void validEntityBeforeSave(PmsProductProperty entity) {
        //TODO 做一些数据校验,如唯一约束
    }

    /**
     * 校验并批量删除商品属性项信息
     *
     * @param ids     待删除的主键集合
     * @param isValid 是否进行有效性校验
     * @return 是否删除成功
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
        if (isValid) {
            for (Long id : ids) {
                // 校验存在
                validatePropertyExists(id);
                // 校验其下是否有规格值
                if (productPropertyValueService.getPropertyValueCountByPropertyId(id) > 0) {
                    throw new ServiceException(PmsErrorCodeConstants.PROPERTY_DELETE_FAIL_VALUE_EXISTS);
                }
            }
        }
        boolean b = baseMapper.deleteBatchIds(ids) > 0;
        if (b) {
            b = productPropertyValueService.deletePropertyValueByPropertyIds(ids);
        }
        return b;
    }

    @Override
    public List<PmsProductProperty> getPropertyList(Set<Long> propertyIds) {
        return baseMapper.selectBatchIds(propertyIds);
    }
}
